﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Net;
using System.IO;
using System.Net.Sockets;
using System.Threading;
using System.Data;
using System.Windows.Forms;


namespace QuickChat
{
    class Connect
    {
        public IPAddress hostIP;
        public User me;
        public int port;
        public int filePort;
        public Thread thread;
        public Thread fileThread;
        UdpClient udpClient;
        ChatForm chatform;
        public bool isContinue = true;

        private void listen()
        {
            udpClient = new UdpClient(port);
            //IPEndPoint receivePoint = new IPEndPoint(hostIP, port);
            IPEndPoint receivePoint = null;
 
            while (isContinue)
            {
                UTF8Encoding encode = new UTF8Encoding();
                byte[] recData = udpClient.Receive(ref receivePoint);
                string result = encode.GetString(recData);
                dealWith(result);
            }
        }

        private void listenFile()
        {
            TcpListenerHelper listener = new TcpListenerHelper(hostIP.ToString(), filePort);
            listener.Start();
            
            while (isContinue)
            {
                listener.Listen();
                try
                {
                    string firstMessage = "";
                    while (!string.IsNullOrEmpty((firstMessage = listener.ReadMessage())))
                    {
                        if (firstMessage == "#sendfile")
                        {
                            string filename = listener.ReadMessage();
                            if (MessageBox.Show("是否接受文件:" + filename + " ?", "Confirm Message", MessageBoxButtons.OKCancel, MessageBoxIcon.Question) == DialogResult.OK)
                            {
                                listener.SendMessage("#sendfileok");
                                string filepath = "../" + filename;
                                listener.ReceiveFile(filepath);
                                listener.SendMessage("#ok");
                                MessageBox.Show("接受成功！");
                            }

                        }
                    }
                }
                catch (Exception e)
                {

                }
            }
            

        }

        private void dealWith(string sr)
        {
            if (sr[0] == '#')
            {
                string[] result = sr.Split(',');
                if (result[0] == "#login")
                {
                    User newUser = new User();
                    newUser.username = result[1];
                    newUser.IP = result[2];
                    online(newUser.IP);
                    somebodyLogin(newUser);
                }
                if (result[0] == "#talk")
                {
                    ChatRecord newRecord = new ChatRecord();
                    newRecord.username = result[1];
                    newRecord.messsage.time = result[2];
                    newRecord.messsage.content = result[3];
                    somebodyTalk(newRecord);
                }
                if (result[0] == "#logout")
                {
                    User deleteUser = new User();
                    deleteUser.username = result[1];
                    deleteUser.IP = result[2];
                    somebodyLogout(deleteUser);
                }
                if (result[0] == "#online")
                {
                    User newUser = new User();
                    newUser.username = result[1];
                    newUser.IP = result[2];
                    somebodyOnline(newUser);
                }
            }
        }

        public delegate void Login(User loginUser);
        public event Login somebodyLogin;

        public delegate void Logout(User logoutUser);
        public event Logout somebodyLogout;

        public delegate void Talk(ChatRecord talkRecord);
        public event Talk somebodyTalk;

        public delegate void Online(User onlineUser);
        public event Online somebodyOnline;

        public Connect(User _me,ChatForm temp)
        {
            chatform = temp;
            port = 7070;
            filePort = 8080;
            me = new User();

            me.IP = _me.IP;
            me.username = _me.username;
            hostIP = IPAddress.Parse(me.IP);
            thread = new Thread(new ThreadStart(listen));
            thread.IsBackground = true;
            thread.Start();
            fileThread = new Thread(new ThreadStart(listenFile));
            fileThread.IsBackground = true;
            fileThread.Start();
        }

        ~Connect()
        {
            //udpClient.Close();
            isContinue = false;
            //fileThread.Abort();
            //thread.Abort();
        }

        public void dispose()
        {
            //udpClient.Close();
            isContinue = false;
            //thread.Abort();
            //fileThread.Abort();
        }

        public bool sendFile(string filePath, string ip)
        {
            TcpClientHelper client = new TcpClientHelper(ip, filePort);
            client.Start();
            client.SendMessage("#sendfile");
            client.SendMessage(Path.GetFileName(filePath));
            if (client.ReadMessage() == "#sendfileok")
            {
                client.SendFile(filePath);
            }

            if (client.ReadMessage() == "#ok")
            {
                MessageBox.Show("发送成功！");
                return true;
            }

            return false;

        }

        public void login()
        {
            Socket sock = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
            sock.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.Broadcast, 1);
            IPEndPoint iep = new IPEndPoint(IPAddress.Broadcast, port);
            byte[] data = Encoding.UTF8.GetBytes("#login," + me.username + "," + me.IP);
            sock.SendTo(data, iep);
            sock.Close();
        }

        public void logout()
        {
            Socket sock = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
            sock.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.Broadcast, 1);
            IPEndPoint iep = new IPEndPoint(IPAddress.Broadcast, port);
            byte[] data = Encoding.UTF8.GetBytes("#logout," + me.username + "," + me.IP);
            sock.SendTo(data, iep);
            sock.Close();
        }

        public void talk(string ip, ChatRecord record)
        {
            IPAddress targrt = IPAddress.Parse(ip);
            UdpClient udpClient = new UdpClient();
            IPEndPoint iep = new IPEndPoint(targrt, port);
            byte[] bytes = Encoding.UTF8.GetBytes("#talk," + record.username + "," + record.messsage.time + "," + record.messsage.content);
            try
            {
                udpClient.Send(bytes, bytes.Length, iep);
                udpClient.Close();
            }
            catch (Exception e)
            {
                Console.WriteLine(e.ToString());
            }
        }

        public void online(string ip)
        {
            IPAddress targrt = IPAddress.Parse(ip);
            UdpClient udpClient = new UdpClient();
            IPEndPoint iep = new IPEndPoint(targrt, port);
            byte[] bytes = Encoding.UTF8.GetBytes("#online," + me.username + "," + me.IP);
            try
            {
                udpClient.Send(bytes, bytes.Length, iep);
                udpClient.Close();
            }
            catch (Exception e)
            {
                Console.WriteLine(e.ToString());
            }
        }

    }
}
